{
Traviesadora beta 0.2.0.13.33 (30.11.2008)
LastMod: 03.12.2008 by Prof1983

Copyright 2008, travieorama@googlemail.com

This file is part of the taviesadora project

taviesadora is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.

taviesadora is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.
}
unit CryptFunctions;

interface

uses
  Classes, SysUtils, ExtCtrls, Windows, Forms, LbCipher, LbClass, LbAsym, LbDSA, LbUtils,
  Service;

const
  KeySizeProt1 = 256;

function DecryptRJDLProt1(msg:string;LbRijndael:TLbRijndael):string;
function EncryptRJDLProt1(msg: string;LbRijndael:TLbRijndael): string;

function KeyStrengthProt1(weakkey:string;Rounds:integer):string;
procedure XORBuffers(var Ares: array of char;B:array of Byte;length:integer);

implementation

procedure XORBuffers(var Ares: array of char;B:array of Byte;length:integer);
var
  i:integer;
begin
  for i := 0 to length-1 do begin
    Ares[i] := chr(B[i] xor ord(Ares[i]));
  end;
end;

function EncryptRJDLProt1(msg: string; LbRijndael: TLbRijndael): string;
var
  c: Byte;
  instream: TMemoryStream;
  outstream: TMemoryStream;
  i: Integer;
  //m: Integer;
begin
  instream := TMemoryStream.Create;
  outstream := TMemoryStream.Create;
  try
    instream.SetSize(length(msg));
    instream.WriteBuffer(msg[1],length(msg));
    for i := 1 to length(msg) do msg[i] := '_';
    c:=0;
    instream.Position := 0;
    LbRijndael.EncryptStream(instream,outstream);
    instream.Position := 0;

    for i := 0 to instream.Size-1 do instream.Write(c,1);
    outstream.Position := 0;
    result := '';
    for i := 0 to outstream.Size-1 do begin
      outstream.Read(c,1);
      result := result+IntToHex(c,2);
    end;
  finally
    instream.Free;
    outstream.Free;
  end;
end;

function DecryptRJDLProt1(msg:string;LbRijndael:TLbRijndael):string;
 var
  instream:TMemoryStream;
  outstream:TMemoryStream;
  i:integer;
  c:Byte;
begin
  instream := TMemoryStream.Create;
  outstream := TMemoryStream.Create;
  try
    result := '';
   instream.Clear;
    outstream.Clear;
    instream.Position := 0;
    while length(msg)>0 do begin
   // for i := 1 to length(msg) div 2 do begin
      if ord(msg[1])<ord('!') then begin
        delete(msg,1,1);
        if ord(msg[1])<ord('!') then begin
          delete(msg,1,1);
        end;
      end;
      c := Byte(hextoint(msg[1]+msg[2]));
      instream.Write(c,1);
      delete(msg,1,2);
    end;
    instream.Position := 0;
    LbRijndael.DecryptStream(instream,outstream);
    outstream.Position := 0;
    for i := 0 to outstream.Size-1 do begin
      outstream.Read(c,1);
      result := result+chr(c);
    end;
    outstream.Seek(0,soFromBeginning);
    c := 0;
    for i := 0 to instream.Size-1 do begin
      outstream.Write(c,1);
    end;
    finally
      instream.Free;
      outstream.Free;
    end;
end;

function KeyStrengthProt1(weakkey: string; Rounds: Integer): string;
var
  //s:string;
  i,n,m:integer;
  key:array[0..(KeySizeProt1 div 8)-1]of char;
  keytxt:array[0..(KeySizeProt1 div 4)]of char;
  md5:TMD5Digest;
  sha1:TSHA1Digest;
  lbMD5:TLbMD5;
  lbSHA1:TLbSHA1;
begin
  lbMD5:= TLbMD5.Create(nil);
  lbSHA1:= TLbSHA1.Create(nil);
  try
    for i := 0 to high(key) do begin
      if length(weakkey) > i then
        key[i] := weakkey[i+1]
      else
        key[i] := #0;
    end;
    for i := 0 to high(keytxt) do begin
      keytxt[i] := #0;
    end;
    for i := 0 to Rounds do begin
      if odd(i) then begin
        for n := 0 to (KeySizeProt1 div 4) div (sizeof(md5) div 2)   {32 div 8} -1 do begin
          lbMD5.HashBuffer(key,sizeof(key));
          lbMD5.GetDigest(md5);
          m := n*(sizeof(md5) div 2)+sizeof(md5);
          if m > sizeof(key) then
            m := sizeof(key)-n*(sizeof(md5) div 2)
          else
            m := sizeof(md5);
          XORBuffers(key[n*(sizeof(md5) div 2)],md5,m);
        end;
      end else begin
        for n := 0 to (KeySizeProt1 div 4) div (sizeof(sha1) div 2)   {32 div 20} -1 do begin
          lbSHA1.HashBuffer(key,sizeof(key));
          lbSHA1.GetDigest(sha1);
          m := n*(sizeof(sha1) div 2)+sizeof(sha1);
          if m > sizeof(key) then
            m := sizeof(key)-n*(sizeof(sha1) div 2)
          else
            m := sizeof(sha1);
          XORBuffers(key[n*(sizeof(sha1) div 2)],sha1,m);
        end;
      end;
    end;
    bintohex(key,keytxt,sizeof(key));
    result := keytxt;
  finally
    lbMD5.Free;
    lbSHA1.Free;
  end;
 end;

end.
